<link rel="import" href="../bower_components/polymer/polymer-element.html">
<link rel="import" href="../bower_components/polymerfire/firebase-auth.html">
<link rel="import" href="../bower_components/polymerfire/firebase-document.html">
<link rel="import" href="../bower_components/polymerfire/firebase-query.html">
<link rel="import" href="../bower_components/app-storage/app-localstorage/app-localstorage-document.html">
<link rel="import" href="../bower_components/paper-toast/paper-toast.html">
<link rel="import" href="../bower_components/paper-checkbox/paper-checkbox.html">
<link rel="import" href="../bower_components/paper-icon-button/paper-icon-button.html">
<link rel="import" href="../bower_components/iron-ajax/iron-ajax.html">
<link rel="import" href="../bower_components/iron-image/iron-image.html">
<link rel="import" href="../bower_components/iron-a11y-keys/iron-a11y-keys.html">
<link rel="import" href="../bower_components/iron-selector/iron-selector.html">
<!-- import style component -->
<link rel="import" href="elements/flat-icons.html">
<link rel="import" href="elements/flat-input.html">
<link rel="import" href="elements/flat-button.html">
<!-- import external library -->
<link rel="import" href="../lib/imask.html">

<dom-module id="view-login">
  <template>
    <style include="flat-input flat-button">
      :host {
        display: block;
        background-color: #ffffff;
      }

      h1,
      h2 {
        margin: 0;
        font-weight: 400;
      }

      p {
        margin: 10px 0;
      }

      section {
        height: 100vh;
        width: 100%;
      }

      article {
        width: 500px;
        margin: 0 auto;
      }

      .flex-container {
        display: flex;
        align-content: center;
        justify-content: space-between;
        flex-flow: row nowrap;
      }

      .flex-item {
        display: flex;
        flex-direction: column;
        justify-content: center;
        flex: 1;
        padding: 1rem;
      }

      .form-title {
        text-align: center;
      }

      .form-title>h2 {
        font-size: 1.5rem;
        margin-bottom: 20px;
      }

      .btn,
      .authen-form {
        width: 100%;
        margin: 10px auto;
      }

      .link>a {
        color: #0070c9;
        margin: 10px 0;
        display: block;
        text-decoration: none;
      }

      .link>a:hover {
        color: #0086f4;
      }

      .link>a:before,
      .link>a:after {
        padding-left: .3em;
        top: 0;
      }

      .logo {
        display: block;
        margin: 10px auto;
        width: 150px;
        height: 150px;
      }

      .keep-session-checkbox {
        margin: 10px 0;
        @apply --layout-horizontal;
      }

      #toastError {
        --paper-toast-background-color: #e53935;
      }

      #toastSuccess {
        --paper-toast-background-color: #43A047;
      }

      .toast {
        --paper-toast-color: #FFFFFF;
        font-size: 1rem;
        width: 100%;
        padding: 16px;
      }

      .toast-flex-container {
        display: -webkit-flex;
        display: flex;
        -webkit-align-self: stretch;
        align-self: stretch;
        justify-content: space-between;
        width: 100%;
        height: auto;
      }

      .toast-flex-item:first-child {
        align-self: stretch;
      }

      .toast-flex-item:last-child {
        align-self: flex-end;
      }

      .toast-flex-item {
        margin: auto 0;
      }

      .close-toast-button {
        text-transform: none;
        float: right;
      }

      @media (min-width: 320px) and (max-width: 767px) {
        .logo {
          display: block;
          margin: 12px auto;
        }
        .form-title>h2 {
          margin-bottom: 5px;
        }
        article {
          width: 90%;
        }
        button {
          font-size: 0.95rem;
        }
        flat-input {
          margin: 0;
        }
        p {
          margin: 5px 0;
        }
      }
    </style>
    <firebase-auth app-name="smart-mes" id="userAuth" user="{{user}}"></firebase-auth>
    <firebase-document app-name="smart-mes" id="userDataTree" path="/user/[[user.uid]]"></firebase-document>
    <firebase-query app-name="smart-mes" id="factoryDataTree" path="/data"></firebase-query>
    <iron-ajax id="requestSampleData" url="data/sample/sample.json" auto handle-as="json" verbose="true" last-response="{{sampleData}}"></iron-ajax>
    <app-localstorage-document key="keep-session" data="{{remember}}"></app-localstorage-document>

    <section class="flex-container">
      <div class="flex-item">
        <article>
          <iron-image preload fade class="logo" role="image" title="IMES" alt="Application logo" sizing="contain" src="images/logo/logo.svg"></iron-image>
          <div hidden$="[[!loginForm]]" class="authen-form">
            <div class="form-title">
              <h2>User Login</h2>
            </div>
            <flat-input>
              <input type="email" id="loginEmail" name="Email" placeholder="Email address" maxlength="30" auto-complete="email" autofocus
                required aria-labelledby="accountEmailLabel" tabindex="0">
              <span class="flat-md-decorator" error-message="Invalid Email" aria-hidden="true">
                <label id="accountEmailLabel">Email address</label>
                <span class="flat-underline"></span>
              </span>
            </flat-input>
            <flat-input>
              <input type="password" id="loginPassword" name="Password" placeholder="Password" maxlength="30" auto-complete="current-password"
                autofocus required aria-labelledby="accountPasswordLabel" tabindex="1" autocomplete="off">
              <span class="flat-md-decorator" error-message="Invalid Input" aria-hidden="true">
                <label id="accountPasswordLabel">Password</label>
                <span class="flat-underline"></span>
              </span>
            </flat-input>
            <div class="keep-session-checkbox">
              <paper-checkbox id="keepSession" checked$="[[remember]]" on-change="toggleKeepSession" noink>Keep me signed in</paper-checkbox>
            </div>
            <flat-button class="btn" on-click="login" title="Login">
              <button tabindex="2">Login</button>
            </flat-button>
            <div class="link">
              <a href="javascript:void(0)" tabindex="4" role="link" on-click="showReset">Forgot?</a>
            </div>
            <div class="link">
              <a href="javascript:void(0)" tabindex="5" role="link" on-click="showRegister">Don’t have an account? Sign up now.</a>
            </div>
          </div>

          <div hidden$="[[!registerForm]]" class="authen-form">
            <div class="form-title">
              <h2>Register</h2>
            </div>
            <flat-input>
              <input type="email" id="register_email" name="Email" placeholder="Email address" maxlength="30" auto-complete="email" required
                aria-labelledby="registerEmailLabel" tabindex="0">
              <span class="flat-md-decorator" error-message="Invalid Email" aria-hidden="true">
                <label id="registerEmailLabel">Email address</label>
                <span class="flat-underline"></span>
              </span>
            </flat-input>
            <flat-input>
              <input type="password" id="register_passwd" name="Password" placeholder="New password" maxlength="30" required aria-labelledby="registerPasswordLabel"
                tabindex="1" autocomplete="off">
              <span class="flat-md-decorator" error-message="Invalid Input" aria-hidden="true">
                <label id="registerPasswordLabel">New password</label>
                <span class="flat-underline"></span>
              </span>
            </flat-input>
            <flat-input>
              <input type="text" id="register_company" name="Company" placeholder="Company" maxlength="30" required aria-labelledby="registerCompanyLabel"
                tabindex="2">
              <span class="flat-md-decorator" error-message="Invalid Input" aria-hidden="true">
                <label id="registerCompanyLabel">Company name</label>
                <span class="flat-underline"></span>
              </span>
            </flat-input>
            <flat-input>
              <input type="tel" id="register_phone" name="Phone" placeholder="Phone" maxlength="15" required aria-labelledby="registerPhoneLabel"
                pattern="^(\+\d{1,2}\s)?\(?\d{4}\)?[\s]?\d{4}[\s]?\d{1}$" onkeypress='return event.charCode >= 48 && event.charCode <= 57 || event.charCode == 43' tabindex="3">
              <span class="flat-md-decorator" error-message="Invalid Phone Number" aria-hidden="true">
                <label id="registerPhoneLabel">Phone (+XX XXXX XXXX X)</label>
                <span class="flat-underline"></span>
              </span>
            </flat-input>
            <div class="link">
              <p>By signing up you agree to IMES’s
                <a href="term" target="_self" id="termOfService" tabindex="4" role="link">Terms of Service</a>
            </div>
            </p>
            <flat-button class="btn" on-click="register" title="Register and Login">
              <button tabindex="5">Register and Login</button>
            </flat-button>
            <div class="link">
              <a href="javascript:void(0)" on-click="hideRegister" tabindex="6" role="link">Already have account? Log in</a>
            </div>
          </div>

          <div hidden$="[[!resetForm]]" class="authen-form">
            <div class="form-title">
              <h2>Reset your password</h2>
              <p>Enter the email you used to signup with and we'll send you a link to reset your password.</p>
            </div>
            <flat-input>
              <input type="email" id="resetPasswordEmail" name="Reset Password E-mail" placeholder="Email address" maxlength="30" auto-complete="email"
                required aria-labelledby="resetPasswordLabel" tabindex="0">
              <span class="flat-md-decorator" error-message="Invalid Email" aria-hidden="true">
                <label id="resetPasswordLabel">Email address</label>
                <span class="flat-underline"></span>
              </span>
            </flat-input>
            <flat-button class="btn" on-click="resetPassword" title="Reset Password">
              <button tabindex="1">Reset Password</button>
            </flat-button>
            <div class="link">
              <a href="javascript:void(0)" rel="noopenner" on-click="hideReset" tabindex="2" role="link">Return to login</a>
            </div>
          </div>
        </article>
      </div>
    </section>
    <paper-toast id="toastSuccess" always-on-top vertical-align="bottom" class="toast fit-bottom" duration="5000">
      <div class="toast-flex-container">
        <div class="toast-flex-item">
          <p>[[successMessage]]</p>
        </div>
        <div class="toast-flex-item">
          <paper-icon-button on-click="closeToastSuccess" class="close-toast-button" icon="icons:close-big" tabindex="-1" noink></paper-icon-button>
        </div>
      </div>
    </paper-toast>
    <paper-toast id="toastError" always-on-top vertical-align="bottom" class="toast fit-bottom" duration="5000">
      <div class="toast-flex-container">
        <div class="toast-flex-item">
          <p>[[errorMessage]]</p>
        </div>
        <div class="toast-flex-item">
          <paper-icon-button on-click="closeToastError" class="close-toast-button" icon="icons:close-big" tabindex="-1" noink></paper-icon-button>
        </div>
      </div>
    </paper-toast>
  </template>
  <script>
    /**
     * @ViewLogins
     * @polymer 
     * @extends {Polymer.Element}
     */
    class ViewLogin extends Polymer.Element {
      static get is() {
        return 'view-login'
      }

      static get properties() {
        return {
          route: {
            type: Object,
            notify: true
          },
          loginForm: {
            type: Boolean,
            value: true
          },
          resetForm: {
            type: Boolean,
            value: false
          },
          registerForm: {
            type: Boolean,
            value: false
          },
          remember: {
            type: Boolean,
            value: true
          },
          sampleData: Object,
          errorMessage: String,
          successMessage: String
        }
      }

      connectedCallback() {
        super.connectedCallback()
        requestAnimationFrame(this._installListeners.bind(this))
      }

      _installListeners() {
        this.$.loginPassword.addEventListener('keydown', (e) => this._onEnterTrigger(e, 0))
        this.$.resetPasswordEmail.addEventListener('keydown', (e) => this._onEnterTrigger(e, 1))
        this.$.termOfService.addEventListener('click', (e) => this.set('route.path', '/term'))
        new IMask(this.$.register_phone, { mask: "+00 0000 0000 0" });
      }

      _onEnterTrigger(e, type) {
        if (e.key !== "Enter") return
        if (type === 0) {
          this.login()
        } else if (type === 1) {
          this.resetPassword()
        }
        e.preventDefault() // No need to `return false`.
      }

      login() {
        if (this.$.loginEmail.value && this.$.loginPassword.value) {
          this.$.userAuth.signInWithEmailAndPassword(this.$.loginEmail.value, this.$.loginPassword.value)
            .then((response) => {
              this.set('route.path', '/dashboard')
            })
            .catch((error) => {
              this._showErrorToast(error.code)
            })
        } else {
          this._showErrorToast('Email or Password cannot leave blank')
        }
      }

      register() {
        const email = this.$.register_email.value
        const company = this.$.register_company.value
        const phone = this.$.register_phone.value
        const password = this.$.register_passwd.value
        const username = 'Untitled'
        if (!this.sampleData) {
          const request = this.$.requestSampleData.generateRequest()
          request.completes.then((req) => {
            console.info('%cLoaded sample data status:' + req.status + " " + req.statusText, 'color:green')
          }).catch((rejected) => {
            let req = rejected.request
            let error = rejected.error
            console.error("Error requesting data: " + error + " of request " + req)
          })
        }
        if (email && company && phone && password && username && this.sampleData) {
          this.$.userAuth.createUserWithEmailAndPassword(email, password)
            .then((response) => {
              this.$.userAuth.signInWithEmailAndPassword(email, password)
                .then((response) => {
                  this.user.updateProfile({
                    displayName: username,
                    phoneNumber: phone
                  })
                  this.user.sendEmailVerification()
                  this._showSuccessToast(
                    "Register successful. We've sent a confirmation link to your email you must follow in order to activate your account."
                  )
                  const keyid = this.$.factoryDataTree.ref.push().key
                  this._addProfileInfo(username, email, company, phone, keyid)
                  this.$.factoryDataTree.ref.child(keyid).set(this.sampleData).catch(error => {
                    console.error(error)
                    this._showErrorToast(error.code)
                  })
                }).catch((error) => {
                  console.error(error)
                  this._showErrorToast(error.code)
                })
            }).catch((error) => {
              console.error(error)
              this._showErrorToast(error.code)
            })
        } else {
          this._showErrorToast('Please fill in the form completely.')
        }
      }

      _addProfileInfo(username, email, company, phone, keyid) {
        this.$.userDataTree.ref.set({
          company: company,
          created: Math.round(Date.now() / 1000),
          displayname: username,
          email: email,
          key: keyid,
          photoURL: null,
          phone: phone,
          role: 'admin',
          setup: false
        }).catch(error => {
          this._showErrorToast(error.code)
        })
      }

      resetPassword() {
        if (this.$.resetPasswordEmail.value) {
          this.$.userAuth.sendPasswordResetEmail(this.$.resetPasswordEmail.value)
            .then((response) => {
              this._showSuccessToast('Reset password link has been send to your email.')
              this.$.resetPasswordEmail.value = ""
            })
            .catch((error) => {
              this._showErrorToast(error.code)
            })
        } else {
          this._showErrorToast('Email cannot leave blank')
        }
      }

      toggleKeepSession() {
        this.remember = !!this.$.keepSession.checked
      }

      showReset() {
        this.resetForm = true
        this.loginForm = false
      }

      hideReset() {
        this.resetForm = false
        this.loginForm = true
      }

      showRegister() {
        this.registerForm = true
        this.loginForm = false
      }

      hideRegister() {
        this.registerForm = false
        this.loginForm = true
      }

      closeToastError(e) {
        this.$.toastError.close()
      }

      closeToastSuccess() {
        this.$.toastSuccess.close()
      }

      _showErrorToast(text) {
        this.errorMessage = text
        this.$.toastError.open()
      }

      _showSuccessToast(text) {
        this.successMessage = text
        this.$.toastSuccess.open()
      }
    }
    window.customElements.define(ViewLogin.is, ViewLogin)
  </script>
</dom-module>